﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Reflection;
using CoreEx.Common.Extensions;
using CoreEx.Common.Reflection;
using LinFu.IoC.Configuration;

namespace CoreEx.Common.Implementation
{
    [Implements(typeof(IBackingFieldRepository),LifecycleType.Singleton)]
    public class BackingFieldRepository : IBackingFieldRepository
    {
        private readonly IDictionary<PropertyInfo,FieldInfo> _fields = new Dictionary<PropertyInfo, FieldInfo>(); 

        
        
        public FieldInfo GetField(PropertyInfo propertyInfo)
        {
            if (!_fields.ContainsKey(propertyInfo))
            {
                var fields =
                propertyInfo.DeclaringType.GetFields(BindingFlags.Instance | BindingFlags.Public |
                                                     BindingFlags.NonPublic);
                var field = fields.Where(f => f.Name.ToUpper().Contains(propertyInfo.Name.ToUpper())).FirstOrDefault();
                if (field == null)
                {
                    var fieldName = propertyInfo.Name.GetBestMatch(fields.Select(f => f.Name));
                    field = fields.Where(f => f.Name == fieldName).FirstOrDefault();
                }
                _fields.Add(propertyInfo,field);
            }

            return _fields[propertyInfo];
        }
    }
}
